Skip to content

clang-tidy: effective config with warnings-as-errors#537

Merged
andiwand merged 4 commits into
mainfrom
clang-tidy-effective-config
Jun 15, 2026
Merged

clang-tidy: effective config with warnings-as-errors#537
andiwand merged 4 commits into
mainfrom
clang-tidy-effective-config

Conversation

@andiwand

Copy link
Copy Markdown
Member

What

Reworks .clang-tidy from the stale CLion template into a high-signal config with WarningsAsErrors, and makes the tree clean under it (all 148 source findings fixed).

Based on pdf-plan-stage1-wrapup (not main) because 8 of the touched files carry unmerged PDF stage-1 changes; retarget to main once that lands.

Config

  • Enable bugprone-*, clang-analyzer-*, performance-*, portability-*.
  • Disable convention-conflict / high-noise checks: avoid-pragma-once, easily-swappable-parameters, narrowing-conversions, enum-size.
  • WarningsAsErrors: '*', but clang-analyzer-* is kept advisory — its only findings are inside third-party -isystem headers (cryptopp/httplib/csv) we can't patch.
  • Removed the dead AnalyzeTemporaryDtors key, which made clang-tidy reject the whole config on every run (the original "noise").
  • test/.clang-tidy disables unchecked-optional-access for tests, where gtest assertion macros defeat the dataflow analysis (false positives only).

Notable code changes

  • bugprone-exception-escape: dropped noexcept from functions that can throw (std::string/filesystem::path allocation), including public API (odr::version, *_to_string, Path accessors). Move ops stay noexcept. CLI main()s wrapped in try/catch.
  • unchecked-optional-access: real restructures (store re-fetched accessors, key ternaries on the optional, add a decryptor guard); NOLINT only for genuine invariants.
  • Mechanical: std::endl'\n', widen-before-multiply, dead forward-decl removal, rewindfseek, string-concat via append, etc.

Verification

  • Clean build (library, tests, CLI) in RelWithDebInfo.
  • clang-tidy 18 (matching CI) reports zero findings on our code.
  • Formatting via clang-format 18.
  • Test suite deferred to CI. Note: HtmlOutputTests.html_meta/* failures observed locally appear pre-existing on this branch (empty meta output, unrelated to these changes).

🤖 Generated with Claude Code

@andiwand andiwand force-pushed the pdf-plan-stage1-wrapup branch from 7ea4ab0 to ee4b884 Compare June 14, 2026 23:17
@andiwand andiwand force-pushed the clang-tidy-effective-config branch from 4066a56 to 1a1b045 Compare June 14, 2026 23:17
@andiwand andiwand force-pushed the pdf-plan-stage1-wrapup branch from ee4b884 to 95520c8 Compare June 15, 2026 07:54
@andiwand andiwand force-pushed the clang-tidy-effective-config branch from 1a1b045 to 5721443 Compare June 15, 2026 07:54
Base automatically changed from pdf-plan-stage1-wrapup to main June 15, 2026 08:28
andiwand and others added 2 commits June 15, 2026 20:25
Rework .clang-tidy from the stale CLion template into a high-signal config
and make the tree clean under it.

Config:
- enable bugprone-*, clang-analyzer-*, performance-*, portability-*
- disable convention-conflicting / high-noise checks (avoid-pragma-once,
  easily-swappable-parameters, narrowing-conversions, enum-size)
- WarningsAsErrors: '*' (clang-analyzer-* kept advisory: its only findings are
  inside third-party -isystem headers)
- drop the removed AnalyzeTemporaryDtors key that made clang-tidy reject the
  whole file on every run
- test/.clang-tidy disables unchecked-optional-access for tests, where gtest
  assertion macros defeat the dataflow analysis (false positives only)

Code fixes (all 148 source findings):
- performance-avoid-endl: std::endl -> '\n'
- bugprone-implicit-widening-of-multiplication-result: widen before multiply
- bugprone-forward-declaration-namespace: drop dead/wrong-namespace fwd decls
- bugprone-reserved-identifier: rename __ throwaways; NOLINT wvware's struct
- bugprone-empty-catch: NOLINT intentional best-effort catches
- bugprone-exception-escape: drop noexcept where functions can throw (string/
  path allocation); keep move ops noexcept; wrap CLI main() in try/catch
- bugprone-unchecked-optional-access: store re-fetched accessors, key ternaries
  on the optional, add a decryptor guard; NOLINT genuine invariants
- misc: inefficient-string-concatenation, unused-local, unsafe-functions
  (rewind -> fseek), optional-value-conversion, macro-parentheses, branch-clone

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
@andiwand andiwand marked this pull request as ready for review June 15, 2026 18:25
@andiwand andiwand force-pushed the clang-tidy-effective-config branch from 5721443 to e391b0b Compare June 15, 2026 18:25
@andiwand andiwand enabled auto-merge (squash) June 15, 2026 18:38
@andiwand andiwand merged commit 6b7e51b into main Jun 15, 2026
11 checks passed
@andiwand andiwand deleted the clang-tidy-effective-config branch June 15, 2026 19:14
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant